/*
 * Segue Audio Player
 * Copyright 2011 Fraser McCrossan frasermccrossan@gmail.com
 * 
 * This program is free software: you can redistribute it and/or modify
 *  it under the terms of the GNU General Public License as published
 *  by the Free Software Foundation, either version 3 of the License,
 *  or (at your option) any later version.
 *
 *  This program is distributed in the hope that it will be useful,
 *  but WITHOUT ANY WARRANTY; without even the implied warranty of
 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 *  GNU General Public License for more details.
 *
 *  You should have received a copy of the GNU General Public License
 *  along with this program.  If not, see <http://www.gnu.org/licenses/>.

 */

package com.frasermccrossan.segue;

import java.util.ArrayList;
import java.util.Set;
import java.util.TreeMap;

import android.content.Context;
import android.database.Cursor;
import android.net.Uri;
import android.provider.MediaStore.Audio.AudioColumns;
import android.util.Log;

/* this reads in the clumsy Android media database into a nice hierarchical structure */

public class TrackRepository {
	
	public static final String TAG = "TrackRepository";
	
//	public class Track {
//		public long _id;
//		public String title;
//		public String artist;
//		public String album;
//		public Integer track;
//		public Integer duration;
//		
//		public Track(long nId, String nTitle, String nArtist, String nAlbum, Integer nTrack, Integer nDuration) {
//			_id = nId;
//			title = nTitle;
//			artist = nArtist;
//			album = nAlbum;
//			track = nTrack;
//			duration = nDuration;
//		}
//		
//		// by default, show title as the string value
//		@Override
//		public String toString() {
//			return track + ". " + title;
//		}
//	}
	
	public TreeMap<CharSequence, TreeMap<CharSequence,ArrayList<Track>>> artist_album_track =
		new TreeMap<CharSequence, TreeMap<CharSequence,ArrayList<Track>>>();
	public TreeMap<CharSequence, ArrayList<Track>> album_track =
		new TreeMap<CharSequence,ArrayList<Track>>();
	
	public TrackRepository(Context context) {
		Uri trackUri = android.provider.MediaStore.Audio.Media.EXTERNAL_CONTENT_URI;
		String proj[] = { AudioColumns._ID,
						  AudioColumns.TITLE,
						  AudioColumns.ARTIST,
						  AudioColumns.ALBUM,
						  AudioColumns.TRACK,
						  AudioColumns.DURATION
						  };
		String sortOrder = AudioColumns.ARTIST + "," + AudioColumns.ALBUM + "," +
			AudioColumns.TRACK + "," + AudioColumns.TITLE;
		Cursor tracks = context.getContentResolver().query(trackUri,
												   		   proj,
												   		   null,
												   		   null,
												   		   sortOrder);
		if (tracks == null) {
			Log.e(TAG, "cursor is null");
			return;
		}
		if (!tracks.moveToFirst()) {
			Log.i(TAG, "no music on device");
			return;
		}
		do {
			Track track = new Track(tracks.getLong(0),
					 				tracks.getString(1),
					 				tracks.getString(2),
					 				tracks.getString(3),
					 				tracks.getInt(4),
					 				tracks.getInt(5));
			addTrack(track);
		} while (tracks.moveToNext());
		tracks.close(); // save memory
	}
	
	public CharSequence[] getArtists() {
		Set<CharSequence> keyset = artist_album_track.keySet();
		return keysetToStringArray(keyset);
	}
	
	public CharSequence[] getAlbums(CharSequence artist) {
		ensureArtistExists(artist);
		Set<CharSequence> keyset = artist_album_track.get(artist).keySet();
		return keysetToStringArray(keyset);
	}

	public Track[] getTracks(CharSequence artist, CharSequence album) {
		ArrayList<Track> tracks;
		ensureArtistAlbumExists(artist, album);
		tracks = artist_album_track.get(artist).get(album);
		return (Track[])tracks.toArray(new Track[tracks.size()]);
	}	
	
	public CharSequence[] getAlbums() {
		Set<CharSequence> keyset = album_track.keySet();
		return keysetToStringArray(keyset);
	}
	
	public Track[] getTracks(CharSequence album) {
		ArrayList<Track> tracks;
		ensureAlbumExists(album);
		tracks = album_track.get(album);
		return (Track[])tracks.toArray(new Track[tracks.size()]);
	}	
	
	private CharSequence[] keysetToStringArray(Set<CharSequence> keyset) {
		return (CharSequence[]) keyset.toArray(new String[keyset.size()]);
	}
	
	private void ensureArtistExists(CharSequence artist) {
		if (!artist_album_track.containsKey(artist)) {
			artist_album_track.put(artist, new TreeMap<CharSequence,ArrayList<Track>>());
		}		
	}
	
	private void ensureArtistAlbumExists(CharSequence artist, CharSequence album) {
		ensureArtistExists(artist);
		if (!artist_album_track.get(artist).containsKey(album)) {
			artist_album_track.get(artist).put(album, new ArrayList<Track>());
		}
	}
	
	private void ensureAlbumExists(CharSequence album) {
		if (!album_track.containsKey(album)) {
			album_track.put(album, new ArrayList<Track>());
		}		
	}
	
	private void addTrack(Track track) {
		ensureArtistAlbumExists(track.artist, track.album);
		artist_album_track.get(track.artist).get(track.album).add(track);
		ensureAlbumExists(track.album);
		album_track.get(track.album).add(track);
		// Log.i(TAG, "added " + track.artist + " > " + track.album + " > " + track.title);
	}
}